package com.hmjk.health.card;

import java.util.ArrayList;
import java.util.Calendar;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import com.hmjk.health.HealthApp;
import com.hmjk.health.R;
import com.hmjk.health.background.NetService;

import android.app.Activity;
import android.app.DatePickerDialog;
import android.app.DatePickerDialog.OnDateSetListener;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.text.format.DateFormat;
import android.text.format.Time;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnTouchListener;
import android.view.ViewGroup;
import android.view.Window;
import android.view.View.OnClickListener;
import android.widget.AbsListView;
import android.widget.AbsListView.OnScrollListener;
import android.widget.BaseAdapter;
import android.widget.DatePicker;
import android.widget.ImageButton;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.TextView;

public class LocationActivity extends Activity implements OnClickListener, OnScrollListener, OnTouchListener{
	private final String TAG = LocationActivity.class.getSimpleName();
	private HealthApp mApp = null;
	private Calendar calendar_from, calendar_to;
	private ListView mList;
	private ArrayList<JSONObject> mLocArray = new ArrayList<JSONObject>();
	private AddressAdapter mAddressAdapter = null;
	
	private int pageIndex = 1; 
	private final int QUERY_PAGE_SIZE = 20;
	private boolean getNext = false;
	private String tid = null, uid = null;
	private long from;
	private long to;
	
	private final long ONE_YEAR_IN_MILLIS = 365L * 24L * 60L * 60L * 1000L;
	private final long ONE_DAY_IN_MILLIS = 1L * 24L * 60L * 60L * 1000L;
	
	private void logd(String info){
		Log.d(TAG,info);
	}
	
	@Override
	public void onCreate(Bundle savedInstanceState) {
		logd("onCreate");
		super.onCreate(savedInstanceState);
		requestWindowFeature(Window.FEATURE_NO_TITLE);
		mApp = (HealthApp)getApplication();
		uid = mApp.getUID();
		tid = this.getIntent().getExtras().getString("tid");
		
		setContentView(R.layout.location_activity);
		
		ImageButton back = (ImageButton)findViewById(R.id.back);
		back.setOnClickListener(this);
		ImageButton search = (ImageButton)findViewById(R.id.search);
		search.setOnClickListener(this);
		
		mList = (ListView)findViewById(R.id.list);
		mAddressAdapter = new AddressAdapter();
		mList.setAdapter(mAddressAdapter);
		
		mList.setOnScrollListener(this);
		mList.setOnTouchListener(this);
		//mList.setClickable(false);
		
		calendar_from = Calendar.getInstance();
		calendar_to = Calendar.getInstance();
		final TextView vFrom = (TextView)findViewById(R.id.from);
		calendar_from.set(calendar_from.get(Calendar.YEAR), calendar_from.get(Calendar.MONTH), calendar_from.get(Calendar.DAY_OF_MONTH), 0, 0, 0);
		vFrom.setText(DateFormat.format("yyyy-MM-dd", calendar_from));
		final TextView vTo = (TextView)findViewById(R.id.to);
		calendar_to.set(calendar_to.get(Calendar.YEAR), calendar_to.get(Calendar.MONTH), calendar_to.get(Calendar.DAY_OF_MONTH), 23, 59, 59);
		vTo.setText(DateFormat.format("yyyy-MM-dd", calendar_to));
		vFrom.setOnClickListener(new OnClickListener() {
			
			@Override
			public void onClick(View arg0) {
				// TODO Auto-generated method stub
				DatePickerDialog dialog = new DatePickerDialog(LocationActivity.this, new OnDateSetListener() {
					
					@Override
					public void onDateSet(DatePicker view, int year, int month, int day) {
						// TODO Auto-generated method stub
						//calendar_from.set(year, month, day);
						calendar_from.set(year, month, day, 0, 0, 0);
						vFrom.setText(DateFormat.format("yyyy-MM-dd", calendar_from));
					}
				}, calendar_from.get(Calendar.YEAR), calendar_from.get(Calendar.MONTH), calendar_from.get(Calendar.DAY_OF_MONTH));
				dialog.show();
			}
		});
		vTo.setOnClickListener(new OnClickListener() {
			
			@Override
			public void onClick(View arg0) {
				// TODO Auto-generated method stub
				DatePickerDialog dialog = new DatePickerDialog(LocationActivity.this, new OnDateSetListener() {
					
					@Override
					public void onDateSet(DatePicker view, int year, int month, int day) {
						// TODO Auto-generated method stub
						//calendar_to.set(year, month, day);
						calendar_to.set(year, month, day, 23, 59, 59);
						vTo.setText(DateFormat.format("yyy-MM-dd", calendar_to));
					}
				}, calendar_to.get(Calendar.YEAR), calendar_to.get(Calendar.MONTH), calendar_to.get(Calendar.DAY_OF_MONTH));
				dialog.show();
			}
		});

	}
	
	class AddressAdapter extends BaseAdapter{
		class ViewHolder{
			public TextView address;
			public TextView timedate;
		}
		
		@Override
		public int getCount() {
			return mLocArray.size();
		}

		@Override
		public Object getItem(int arg0) {
			// TODO Auto-generated method stub
			return null;
		}

		@Override
		public long getItemId(int arg0) {
			// TODO Auto-generated method stub
			return 0;
		}

		@Override
		public View getView(int pos, View itemView, ViewGroup group) {
			ViewHolder holder;
			
			if(itemView == null){
				LayoutInflater inflater = getLayoutInflater();
				itemView = inflater.inflate(R.layout.history_address_item, null);
				holder = new ViewHolder();
				
				holder.address = (TextView)itemView.findViewById(R.id.item_address);
				holder.timedate = (TextView)itemView.findViewById(R.id.item_time);
				
				itemView.setTag(holder);
			}else{
				holder = (ViewHolder)itemView.getTag();
			}
			
			try {
				JSONObject e = mLocArray.get(pos);
				String addr = "";
				if(e.has("addr"))
				  addr = e.getString("addr");
				long time = e.getLong("time");
				Time t = new Time();
				t.setToNow();
				t.set(time);
				String monstr = String.format("%02d", t.month+1);
				String daystr = String.format("%02d", t.monthDay);
				String hourstr = String.format("%02d", t.hour);
				String minutestr = String.format("%02d", t.minute);
				String secondstr = String.format("%02d", t.second);
				String timestr = getResources().getString(R.string.addr_date_time, t.year, monstr, daystr
						,hourstr, minutestr, secondstr);
				Log.d("LocationActivity", "addr:" + addr);
				Log.d("LocationActivity", "timestr" + timestr);
				holder.address.setText(addr);
				holder.timedate.setText(timestr);
			} catch (JSONException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			
			
			
			return itemView;
		}
	
	}
	
	private Handler mHandler = new Handler(){
		@Override
		public void handleMessage(Message msg){
			switch(msg.what){
			case HealthApp.MSG_NET_RESPONSE:{
				logd("MSG_NET_RESPONSE");
				Bundle b = msg.getData();
				String stamp = b.getString("stamp","ooh!No!");
				if(stamp.startsWith("GET_HISTORY_LOCATION")){
					String sjson = b.getString("json");
					if(sjson != null){
						mApp.dismissWaiting();
						getNext = false;
						
						try {
							JSONObject json = new JSONObject(sjson);
							int code = json.getInt("code");
							JSONObject sd = json.getJSONObject("senddata");
							if(sd != null)
								tid = sd.getString("tid");
							if(code == 200){
								String state = json.getString("state");
								if(state.equalsIgnoreCase("00")){
									if(pageIndex == 1){
										mLocArray.clear();
									}
									JSONObject recdata = json.getJSONObject("recdata");
									if(recdata != null){
										if(recdata.has("position")){
											JSONArray arr = recdata.getJSONArray("position");
											int len = arr.length();
											Log.d(TAG, "GET SIZE = " + len);
											if(len < QUERY_PAGE_SIZE){
												Log.d(TAG, "NO DATA MORE");
												getNext = false;
											}else{
												Log.d(TAG, "DATA MORE");
												getNext = true;
											}
											for(int i = 0; i < len; i++){
												JSONObject o = arr.getJSONObject(i);
												mLocArray.add(o);
											}
										}else{
											Log.d(TAG, "2 NO DATA MORE");
											getNext = false;
										}
									}
									mAddressAdapter.notifyDataSetChanged();
								}else if(state.equals("01")){
									if(pageIndex == 1){
										mLocArray.clear();
									}
									mAddressAdapter.notifyDataSetChanged();
									mApp.showAlertDialog(LocationActivity.this, R.string.server_noResp);
								}
								return;
							}
						} catch (JSONException e) {
							// TODO Auto-generated catch block
							e.printStackTrace();
						}
						if(pageIndex == 1){
							mLocArray.clear();
						}
						mAddressAdapter.notifyDataSetChanged();
						mApp.showAlertDialog(LocationActivity.this, R.string.history_err);
					}
				}
			}break;
			}
		}
	};

	private void doSearchHistoryLocation(){	
		mApp.showWaitting(this, null);
		Intent si = new Intent(NetService.GET_DATA_ACTION);
		si.putExtra("sub_act", NetService.GET_DEVICE_LOCATION_PAGE);
		si.putExtra("uid", uid);
		si.putExtra("tid", tid);
		si.putExtra("endtime", to);
		si.putExtra("starttime", from);
		si.putExtra("pageindex", String.valueOf(pageIndex));
		si.putExtra("pagesize", String.valueOf(QUERY_PAGE_SIZE));
		
		Time t = new Time();
		t.setToNow();
		String stamp = "GET_HISTORY_LOCATION" + t.toString();
		si.putExtra("stamp",stamp);
		mApp.addNetHandler(stamp, mHandler);
		startService(si);
	}
	
	@Override
	public void onClick(View v) {
		// TODO Auto-generated method stub
		switch(v.getId()){
		case R.id.back:{
			finish();
		}break;
		
		case R.id.search:{
			long time_from = calendar_from.getTimeInMillis();
			long time_to = calendar_to.getTimeInMillis();
			long time_now = System.currentTimeMillis();
			long itime = 0;
			
			if(time_from >= time_to){
				mApp.showAlertDialog(LocationActivity.this, R.string.history_err_edit);
				return;
			}
			if(time_from >= time_now){
				mApp.showAlertDialog(LocationActivity.this, R.string.history_err_edit);
				return;
			}
			if(time_to >= time_now){
				itime = time_to - time_now;
				if(itime > ONE_DAY_IN_MILLIS){
					mApp.showAlertDialog(LocationActivity.this, R.string.history_err_edit);
					return;
				}
			}
			itime = time_now - time_from;
			if(itime > ONE_YEAR_IN_MILLIS){
				mApp.showAlertDialog(LocationActivity.this, R.string.history_err_oneyear);
				return;
			}
			
			pageIndex = 1;
			from = time_from;
			to = time_to;
			doSearchHistoryLocation();
			
		}break;
		}
	}
	
	
	/*OnScrollListener start*/
	private boolean listBottom = false;
	@Override
	public void onScroll(AbsListView arg0, int firstV, int vCount, int total) { 
		 if(margin > 0)
			 return;
		 
         if (firstV + vCount == total && total > 0) { 
        	 int lb = mList.getBottom();
        	 int lt = mList.getTop();
        	 int count = mList.getChildCount();
        	 View bottomView = mList.getChildAt(count -1);
        	 int bb = bottomView.getBottom();
        	 bb += lt;
        	 //int bt = bottomView.getTop();
        	 if (lb >= bb){
        		 if(!listBottom){		
	        		 listBottom = true;  
	        		 Log.d("PULL_DEBUG", "LIST BOTTOM");
	        	 }
             }else{
            	if(listBottom){
        			 listBottom=false;
        			 Log.d("PULL_DEBUG", "NOT LIST BOTTOM");
        		} 
             }

         }else{
        	 if(listBottom){
        	 listBottom=false;
        	 Log.d("PULL_DEBUG", "NOT LIST BOTTOM");
        	 }
         }  
	}  

	@Override
	public void onScrollStateChanged(AbsListView v, int scrollState) {
		Log.d("PULL_DEBUG", "scrollState = "+ scrollState);
	}
	/*OnScrollListener end*/

	/*OnTouchListener start*/
	private float down_y=0f;
	//private boolean pull = false;
	private int margin = 0;
	@Override
	public boolean onTouch(View v, MotionEvent e) {
		
        float density = getResources().getDisplayMetrics().density; 
        LinearLayout.LayoutParams pullLp = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, 
        		LinearLayout.LayoutParams.WRAP_CONTENT);  
        Log.d("PULL_DEBUG", "TOUCH ACTION="+e.getAction());
        switch(e.getAction()){  
        case MotionEvent.ACTION_DOWN:   
            down_y = e.getY();
            break;  
        case MotionEvent.ACTION_MOVE:  
        	float y_dis = down_y - e.getY(); 
        	y_dis = y_dis/4;
        	Log.d("PULL_DEBUG", "dis="+y_dis+" listBottom="+listBottom);
        	if(listBottom && y_dis > 0){  		
        		Log.d("PULL_DEBUG", "PULL DOWN");
        		float distance=Math.abs(y_dis/density + 0.5f);  
        		pullLp.bottomMargin = margin =(int)distance;  
        		Log.d("PULL_DEBUG", "PULL DOWN margin= "+margin);
                mList.setLayoutParams(pullLp);  
              
        	}else if(margin > 0){
        		pullLp.bottomMargin = margin = 0;  
    			mList.setLayoutParams(pullLp);
        		Log.d("PULL_DEBUG", "NOT PULL DOWN");
        		//pull = false;
        	}
        	break;  
        case MotionEvent.ACTION_UP: 
        case MotionEvent.ACTION_CANCEL:
        	if(margin > 0){
        		//if(listBottom){  
        		if(margin > 40){
        			if(!getNext){
                		Log.d("PULL_DEBUG", "NO NEXT");
                	}else{
                		Log.d("PULL_DEBUG", "CHECKING..");
                		pageIndex++;
                		
                		doSearchHistoryLocation();
                	}
        		}
        			pullLp.bottomMargin = margin = 0;  
        			mList.setLayoutParams(pullLp);
        			
        			
               // }   
        		
        	}
        	//pull = false;
        	//listBottom = false;
            break;  
        }  
        
		return false;
	}
	/*OnTouchListener end*/
}
